package com.boco.pciv.core.aop;

import cn.hutool.core.util.ClassUtil;
import cn.hutool.json.JSONUtil;
import com.boco.pciv.core.annotion.NoAopLog;
import com.boco.pciv.core.util.ToolUtil;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Pointcut;
import org.aspectj.lang.reflect.MethodSignature;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.core.annotation.Order;
import org.springframework.stereotype.Component;

import java.util.Arrays;
import java.util.List;

@Aspect
@Component
@Order(3)
public class ServiceLogAop {

	private  static Logger logger = LoggerFactory.getLogger(ServiceLogAop.class);

	@Pointcut("execution(*  com.boco.pciv.service..*.*(..)) || execution(*  com.boco.pciv.core.service..*.*(..))")
	private  void allServiceMethod(){

	}

//	@Before("allServiceMethod()")
//	public void before(JoinPoint jp){
//		List list=Arrays.asList(jp.getArgs());
//
//		if (logger.isInfoEnabled()){
//			logger.info("[{}-{}]  args:{}", ClassUtil.getShortClassName(jp.getTarget().getClass().getName()),jp.getSignature().getName(),JSONUtil.toJsonStr(list));
//		}
//	}
//	@AfterReturning(pointcut="allServiceMethod()", returning="retVal")
//	public void afterReturn(JoinPoint  jp,Object retVal){
//		long time=System.currentTimeMillis() - startTime.get();
//		logger.info("Services Method:[{}] castTime:[{}ms]",jp.getSignature().getName(),time );
//	}

	@Around("allServiceMethod()")
	public Object around(ProceedingJoinPoint pjp) throws Throwable{
		List list=Arrays.asList(pjp.getArgs());
		String shortClassName = ClassUtil.getShortClassName(pjp.getTarget().getClass().getName());
		String methodName = pjp.getSignature().getName();
		if (logger.isInfoEnabled()){
			logger.info("[{}-{}] args:{}", shortClassName,methodName,JSONUtil.toJsonStr(list));
		}

		Object result = null;
		long start = System.currentTimeMillis();
		//有返回参数 则需返回值
		result =  pjp.proceed();
		long end = System.currentTimeMillis();

		//跳过服务
		NoAopLog annotation = pjp.getTarget().getClass().getAnnotation(NoAopLog.class);
		if (annotation!= null){
			return result;
		}
		NoAopLog annotation1 = ((MethodSignature)pjp.getSignature()).getMethod().getAnnotation(NoAopLog.class);
		if (annotation1!= null){
			return result;
		}
		logger.info("[{}-{}] castTime:{}ms",shortClassName,methodName, end - start);
		if (logger.isDebugEnabled()) {
			String resultStr;
			if(result==null) {
				resultStr = "";
			}
			else if (ToolUtil.isSimpleValueType(result.getClass())){
				resultStr = result.toString();
			} else{
				resultStr = JSONUtil.toJsonStr(result);
			}
			logger.debug("[{}-{}] result:{}",shortClassName,methodName, resultStr);
		}
		return result;
	}
}
